/**
 * CC2003 - Worksheet 3 - Queues in a Bank
 * 
 * For the course CC2003 - Algorithms and Data Structures of UVG (Universidad del Valle de Guatemala, http://uvg.edu.gt)
 * 
 * 
 * SVN Repository of my course projects: http://cc2003.svn.sourceforge.net/viewvc/cc2003/
 * 
 * 
 * Copyright (C) 2009 Carlos Lopez Camey
 * visit me at http://kmels.net or write me at c.lopez@kmels.net
 * 
 * 
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 * 
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *  
 *  You should have received a copy of the GNU General Public License
 *  along with this program.  If not, see <http://www.gnu.org/licenses/> or write to the Free Software Foundation, Inc.,
 *  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
 */

package estructuras;

/**
 * @author kmel
 *
 */
public class QueueUsingCircularList<TypeOfTheElements> extends MoculatorQueue<TypeOfTheElements>{
	private Node<TypeOfTheElements> tail;
	Node<TypeOfTheElements> last;
	
	public QueueUsingCircularList(){
		this.setTail(new Node(null,null));
		this.nelements = 0;
		this.last = this.getTail();
	}
	
	@Override
	public void add(TypeOfTheElements Element) throws FullQueueException {
		if (this.isFull())
			throw new FullQueueException();
		
		
		this.last.next = new Node(this.last,this.getTail(),Element);
		this.last = this.last.next;
		this.nelements++;
	}

	/*
	 * 
	 * @return the first element of the queue
	 * @see BankQueue#peek()
	 */
	@Override
	public TypeOfTheElements peek() throws EmptyQueueException {
		if (this.isEmpty())
			throw new EmptyQueueException();
		
		return this.getTail().next.value;
	}

	@Override
	public TypeOfTheElements remove() throws EmptyQueueException {
		if (this.isEmpty())
			throw new EmptyQueueException();
		
		TypeOfTheElements returnValue = this.peek();
		
		if (this.nelements == 1){
			this.last = this.getTail();
		}
		else
			this.getTail().next = this.getTail().next.next;
		
		this.nelements--;
		return returnValue;
	}

	@Override
	public String toString() {
		String response = "";
		response += "Esta cola tiene " + nelements + " elementos dentro";
		
		Node<TypeOfTheElements> currentNode = this.getTail().next;
		
		while (currentNode.value != null){
			response += currentNode.value.toString();
			currentNode = currentNode.next;
		}
		
		return response;
	}

	/**
	 * @param tail the tail to set
	 */
	public void setTail(Node<TypeOfTheElements> tail) {
		this.tail = tail;
	}

	/**
	 * @return the tail
	 */
	public Node<TypeOfTheElements> getTail() {
		return tail;
	}

	
}
